package com.atguigu.tingshu.order.strategy.impl;

import com.atguigu.tingshu.account.client.UserAccountFeignClient;
import com.atguigu.tingshu.common.constant.KafkaConstant;
import com.atguigu.tingshu.common.constant.SystemConstant;
import com.atguigu.tingshu.common.execption.GuiguException;
import com.atguigu.tingshu.common.result.Result;
import com.atguigu.tingshu.common.result.ResultCodeEnum;
import com.atguigu.tingshu.common.service.KafkaService;
import com.atguigu.tingshu.common.util.AuthContextHolder;
import com.atguigu.tingshu.model.order.OrderDerate;
import com.atguigu.tingshu.model.order.OrderDetail;
import com.atguigu.tingshu.model.order.OrderInfo;
import com.atguigu.tingshu.order.mapper.OrderDerateMapper;
import com.atguigu.tingshu.order.mapper.OrderDetailMapper;
import com.atguigu.tingshu.order.mapper.OrderInfoMapper;
import com.atguigu.tingshu.order.service.OrderInfoService;
import com.atguigu.tingshu.order.strategy.SaveOrderStrategy;
import com.atguigu.tingshu.vo.account.AccountLockResultVo;
import com.atguigu.tingshu.vo.account.AccountLockVo;
import com.atguigu.tingshu.vo.order.OrderDetailVo;
import com.atguigu.tingshu.vo.order.OrderInfoVo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.util.UUID;


// 余额支付保存订单策略接口方法
@Service
@Slf4j
public class AccountSaveOrderStrategy implements SaveOrderStrategy {

    @Autowired
    private UserAccountFeignClient  userAccountFeignClient;

    @Autowired
    private OrderInfoMapper orderInfoMapper;

    @Autowired
    private OrderDetailMapper orderDetailMapper;

    @Autowired
    private OrderDerateMapper orderDerateMapper;

    @Autowired
    private KafkaService kafkaService;

    @Autowired
    private OrderInfoService orderInfoService;

    @Override
    public OrderInfoVo saveOrder(OrderInfoVo orderInfoVo) {
        // 获取当前登录用户的id
        Long userId = AuthContextHolder.getUserId();
        // 生成一个新的外部交易号
        String orderNo = UUID.randomUUID().toString().replace("-" , "") ;
        // 创建AccountLockVo对象，封装远程调用所需要的数据
        AccountLockVo accountLockVo = new AccountLockVo() ;
        accountLockVo.setOrderNo(orderInfoVo.getTradeNo());
        accountLockVo.setUserId(userId);
        accountLockVo.setAmount(orderInfoVo.getOrderAmount());
        OrderDetailVo orderDetailVo = orderInfoVo.getOrderDetailVoList().get(0);
        accountLockVo.setContent(orderDetailVo.getItemName());


        //远程调用useraccount
        Result<AccountLockResultVo> accountLockResultVoResult = userAccountFeignClient.checkAndLock(accountLockVo);
        Integer code = accountLockResultVoResult.getCode();
        //余额锁定失败
        if (!code.equals(200)){
            throw new GuiguException(ResultCodeEnum.ACCOUNT_LESS) ;
        }
        try {

            // 保存的订单相关数据: 订单的基本数据、订单的明细数据、订单的减免明细数据
            this.saveOrderInfoAndDetailAndDerateInfo(orderInfoVo , orderInfoMapper , orderDetailMapper , orderDerateMapper);
        }catch (Exception e) {
            e.printStackTrace();
            kafkaService.sendMessage(KafkaConstant.QUEUE_ACCOUNT_UNLOCK , orderInfoVo.getTradeNo());        // 向kafka中发送解锁账户金额的消息
            throw new GuiguException(ResultCodeEnum.SERVICE_ERROR) ;

        }

        // 返回
        return orderInfoVo;

    }




    @Override
    public String getPayWay() {
        return SystemConstant.ORDER_PAY_ACCOUNT;
    }

    @Override
    public void saveOrderAfterProcess(OrderInfoVo orderInfoVo) {
        // 保存交易信息(user_paid_album、user_paid_track、user_vip_service)
        orderInfoService.orderPaySuccess(orderInfoVo.getTradeNo()) ;

        // 扣减账户的余额
        kafkaService.sendMessage(KafkaConstant.QUEUE_ACCOUNT_MINUS , orderInfoVo.getTradeNo());
    }
}
